package pers.xhh.frontapi.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.BoundHashOperations;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import pers.xhh.frontapi.common.Constant;
import pers.xhh.frontapi.common.Mi;
import pers.xhh.frontapi.common.ResultCode;
import pers.xhh.frontapi.entity.MiUserEntity;
import pers.xhh.frontapi.entity.MiWareEntity;
import pers.xhh.frontapi.entity.to.cart.CartTo;
import pers.xhh.frontapi.entity.vo.cart.CartItem;
import pers.xhh.frontapi.entity.vo.cart.CartVo;
import pers.xhh.frontapi.entity.vo.goods.MiGoodsPutVo;
import pers.xhh.frontapi.interceptor.AuthenticationInterceptor;
import pers.xhh.frontapi.service.CartService;
import pers.xhh.frontapi.service.MiGoodsService;
import pers.xhh.frontapi.service.MiWareService;

import java.math.BigDecimal;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * @author wei-xhh
 * @date 2020-12-08
 */
@Service
public class CartServiceImpl implements CartService {

    @Autowired
    StringRedisTemplate redisTemplate;

    @Autowired
    MiGoodsService miGoodsService;

    @Autowired
    MiWareService miWareService;

    @Override
    public Mi addToCart(CartTo cartTo) throws JsonProcessingException {
        Integer goodsId = cartTo.getGoodsId();
        Integer num = cartTo.getNum();
        // 添加商品的属性
        String attr = cartTo.getAttr();
        if (goodsId == null || num == null) {
            return Mi.error(ResultCode.ERROR1002.getMessage(), ResultCode.ERROR1002.getStatus());
        }
        if (goodsId <= 0 || num <= 0) {
            return Mi.error(ResultCode.ERROR1002.getMessage(), ResultCode.ERROR1002.getStatus());
        }

        BoundHashOperations<String, Object, Object> cartOps = getCartOps();

        String res = (String) cartOps.get(goodsId.toString());
        if (res == null || res.isEmpty()) {
            // 购物车没有该商品

            // ->根据商品id查询商品
            CartItem cartItem = new CartItem();
            Mi goodsInfo = miGoodsService.getGoodsById(goodsId);
            MiGoodsPutVo miGoodsVo =
                    (MiGoodsPutVo) goodsInfo.getData();
            MiWareEntity miWareEntity =
                    miWareService.getOne(new QueryWrapper<MiWareEntity>().eq("goods_id", goodsId));
            if (miWareEntity != null) {
                Integer stock = miWareEntity.getStock();
                Integer stockLocked = miWareEntity.getStockLocked();
                cartItem.setWareCount(stock - stockLocked);
            }
            // ->商品添加到购物车
            cartItem.setCheck(true);
            cartItem.setCount(1);
            // 商品图片
            String pic = miGoodsVo.getPics().get(0).getPic();
            if (pic == null) {
                pic = "";
            }
            cartItem.setImage(pic);
            cartItem.setTitle(miGoodsVo.getGoods_name());
            cartItem.setPrice(miGoodsVo.getGoods_price());
            // ->保存attr
//            List<Map<String, Object>> attrs = miGoodsVo.getAttrs();
//            List<String> attr = new ArrayList<>();
//            for (Map<String, Object> map : attrs) {
//                String attrValue =
//                        (String) map.get("attr_value");
//                attr.add(attrValue);
//            }

            cartItem.setAttr(attr);
            cartItem.setGoodsId(miGoodsVo.getGoods_id());
            // ->保存
            ObjectMapper objectMapper = new ObjectMapper();
            cartOps.put(goodsId.toString(),
                    objectMapper.writeValueAsString(cartItem));

        } else {
            // 购物车有此商品,修改数据
            ObjectMapper objectMapper = new ObjectMapper();
            CartItem cartItem = objectMapper.readValue(res, CartItem.class);
            cartItem.setCount(cartItem.getCount() + num);

            cartOps.put(goodsId.toString(),
                    objectMapper.writeValueAsString(cartItem));

        }
        return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), "添加成功");

    }

    @Override
    public Mi getCartItem(Integer goodsId) throws JsonProcessingException {
        if (goodsId == null) {
            return Mi.error(ResultCode.ERROR1002.getMessage(), ResultCode.ERROR1002.getStatus());
        }

        BoundHashOperations<String, Object, Object> cartOps = getCartOps();
        String o = (String) cartOps.get(goodsId.toString());
        ObjectMapper objectMapper = new ObjectMapper();
        CartItem cartItem = objectMapper.readValue(o, CartItem.class);

        return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), cartItem);
    }

    @Override
    public Mi getCartList() {

        CartVo cartVo = new CartVo();

        // 获取登录后的信息
        MiUserEntity miUserEntity =
                AuthenticationInterceptor.threadLocal.get();

        String cartKey = Constant.CART_PREFIX + miUserEntity.getUserId();
        BoundHashOperations<String, Object, Object> cartOps = redisTemplate.boundHashOps(cartKey);
        List<Object> values = cartOps.values();
        int selectCount = 0;
        if (values != null && values.size() > 0) {
            List<CartItem> collect = values.stream().map((obj) -> {
                String str = (String) obj;
                ObjectMapper objectMapper = new ObjectMapper();
                CartItem cartItem = new CartItem();
                try {
                    cartItem = objectMapper.readValue(str, CartItem.class);
                } catch (JsonProcessingException e) {
                    e.printStackTrace();
                }
                return cartItem;
            }).collect(Collectors.toList());
            cartVo.setItems(collect);

            for (CartItem cartItem : collect) {
                if (cartItem.getCheck()) {
                    selectCount++;
                }
            }
        }

        Map<String, Object> map = new HashMap<>();
        map.put("selectCount", selectCount);
        map.put("countNum", cartVo.getCountNum());
        map.put("countType", cartVo.getCountType());
        map.put("totalAmount", cartVo.getTotalAmount());
        map.put("items", cartVo.getItems());

        return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), map);
    }

    @Override
    public Mi clearCart() {
        // 获取登录后的信息
        MiUserEntity miUserEntity =
                AuthenticationInterceptor.threadLocal.get();

        String cartKey = Constant.CART_PREFIX + miUserEntity.getUserId();
        Boolean delete = redisTemplate.delete(cartKey);
        if (delete) {
            return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), "购物车已清空！");
        } else {
            return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), "购物车为空！");
        }

    }

    /**
     * 勾选购物项
     *
     * @param goodsId
     * @param check
     * @return
     */
    @Override
    public Mi selectItem(Integer goodsId, Integer check) throws JsonProcessingException {
        if (goodsId == null || check == null) {
            return Mi.error(ResultCode.ERROR1002.getMessage(), ResultCode.ERROR1002.getStatus());
        }
        if (goodsId <= 0) {
            return Mi.error(ResultCode.ERROR1002.getMessage(), ResultCode.ERROR1002.getStatus());
        }

        BoundHashOperations<String, Object, Object> cartOps = getCartOps();
        String o = (String) cartOps.get(goodsId.toString());
        ObjectMapper objectMapper = new ObjectMapper();
        CartItem cartItem = objectMapper.readValue(o, CartItem.class);
        cartItem.setCheck(check == 1 ? true : false);
        String s = objectMapper.writeValueAsString(cartItem);
        cartOps.put(goodsId.toString(), s);
        return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), "修改选中成功！");
    }

    @Override
    public Mi addCartCount(Integer goodsId, Integer num) throws JsonProcessingException {

        if (goodsId == null || num == null) {
            return Mi.error(ResultCode.ERROR1002.getMessage(), ResultCode.ERROR1002.getStatus());
        }
        if (goodsId <= 0 || num <= 0) {
            return Mi.error(ResultCode.ERROR1002.getMessage(), ResultCode.ERROR1002.getStatus());
        }

        BoundHashOperations<String, Object, Object> cartOps = getCartOps();
        String o = (String) cartOps.get(goodsId.toString());
        ObjectMapper objectMapper = new ObjectMapper();
        CartItem cartItem = objectMapper.readValue(o, CartItem.class);
        cartItem.setCount(num);
        BigDecimal totalPrice = cartItem.getTotalPrice();
        // 乘以数量后的总价
        BigDecimal multiply = totalPrice.multiply(BigDecimal.valueOf(num));
        cartItem.setTotalPrice(multiply);
        cartOps.put(goodsId.toString(), objectMapper.writeValueAsString(cartItem));
        return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), "改变数量成功！");
    }

    @Override
    public Mi deleteCartItem(Integer goodsId) {
        BoundHashOperations<String, Object, Object> cartOps = getCartOps();
        cartOps.delete(goodsId.toString());
        return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), "删除成功！");
    }

    @Override
    public Mi selectAll() {
        boolean b = changeAllCheck(true);
        if (b) {
            return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), "全部中成功！");
        } else {
            return Mi.error(ResultCode.ERROR1003.getMessage(), ResultCode.ERROR1003.getStatus());
        }

    }

    @Override
    public Mi doneAll() {
        boolean b = changeAllCheck(false);
        if (b) {
            return Mi.ok(ResultCode.SUCCESS.getMessage(), ResultCode.SUCCESS.getStatus(), "删除全部成功！");
        } else {
            return Mi.error(ResultCode.ERROR1003.getMessage(), ResultCode.ERROR1003.getStatus());
        }
    }

    /**
     * 选中或不选中全部
     *
     * @param change
     */
    private boolean changeAllCheck(boolean change) {
        BoundHashOperations<String, Object, Object> cartOps = getCartOps();
        List<Object> values = cartOps.values();
        if(values != null && values.size() > 0){
            for (Object value : values) {
                String str = (String) value;
                ObjectMapper objectMapper = new ObjectMapper();
                try {
                    CartItem cartItem = objectMapper.readValue(str, CartItem.class);
                    cartItem.setCheck(change);
                    Integer goodsId = cartItem.getGoodsId();
                    String s = objectMapper.writeValueAsString(cartItem);
                    cartOps.put(goodsId.toString(), s);
                } catch (JsonProcessingException e) {
                    e.printStackTrace();
                }
            }
            return true;
        }
        return false;
    }

    /**
     * 获取要操作的购物车
     *
     * @return
     */
    private BoundHashOperations<String, Object, Object> getCartOps() {
        // 获取登录后的信息
        MiUserEntity miUserEntity =
                AuthenticationInterceptor.threadLocal.get();
        // ->保存到redis中的key
        String cartKey = Constant.CART_PREFIX + miUserEntity.getUserId();

        BoundHashOperations<String, Object, Object>
                hashOps = redisTemplate.boundHashOps(cartKey);

        return hashOps;
    }
}
